#include "Vector2D.h"
#include <math.h>

#define PI 3.14159265

using namespace TP::Matematica;

Vector2D::Vector2D() {
	this->_x = 0;
	this->_y = 0;
}

Vector2D::Vector2D(double pX, double pY) {
	this->_x = pX;
	this->_y = pY;
}

Vector2D::~Vector2D() { }

double Vector2D::X() const {
	return this->_x;
}

double Vector2D::X(double pX) {
	this->_x = pX;
	return pX;
}

double Vector2D::Y() const {
	return this->_y;
}

double Vector2D::Y(double pY) {
	this->_y = pY;
	return pY;
}

string Vector2D::aXML() {
	TiXmlDocument* doc = new TiXmlDocument();
	TiXmlDeclaration * decl = new TiXmlDeclaration("1.0", "", "");
	doc->LinkEndChild(decl);

	doc->LinkEndChild(this->aElementoXML());

	TiXmlPrinter printer;
	doc->Accept(&printer);
	return printer.CStr();
}

string Vector2D::aXML(const string& pPath) {
	TiXmlDocument* doc = new TiXmlDocument(pPath.c_str());
	TiXmlDeclaration * decl = new TiXmlDeclaration("1.0", "", "");
	doc->LinkEndChild(decl);

	doc->LinkEndChild(this->aElementoXML());

	TiXmlPrinter printer;
	doc->Accept(&printer);
	return printer.CStr();
}

void Vector2D::parseXML(const string& pDescriptor) {
	TiXmlDocument doc;
	doc.Parse(pDescriptor.c_str(), 0, TIXML_ENCODING_UTF8);
	this->deElementoXML(doc.FirstChildElement());
}

TiXmlElement* Vector2D::aElementoXML() {
	TiXmlElement * element = new TiXmlElement("Vector2D");

	element->SetDoubleAttribute("x", this->_x);
	element->SetDoubleAttribute("y", this->_y);

	return element;
}

void Vector2D::deElementoXML(TiXmlElement* pElemento) {
	if (strcmp(pElemento->Value(), "Vector2D") == 0) {
		pElemento->Attribute("x", &this->_x);
		pElemento->Attribute("y", &this->_y);
	}
}

double Vector2D::norma() const {
	return sqrt(pow(this->_x, 2) + pow(this->_y, 2));
}

double Vector2D::operator*(const Vector2D& pOperando) {
	return _x * pOperando._x + _y * pOperando._y;
}

const Vector2D Vector2D::operator*(double pEscalar)const {
	Vector2D resultado;
	resultado._x = _x * pEscalar;
	resultado._y = _y * pEscalar;
	return resultado;
}

const Vector2D Vector2D::direccion() const {
	Vector2D vector = (*this) * (1 / (*this).norma());
	return vector;
}

Vector2D Vector2D::operator=(const Vector2D pOperando) {
	if (&pOperando == this)
		return *this;

	_x = pOperando._x;
	_y = pOperando._y;
}

const Vector2D Vector2D::operator+(const Vector2D& pOperando) const {
	Vector2D vector = *this;
	vector._x += pOperando._x;
	vector._y += pOperando._y;
	return vector;
}

const Vector2D Vector2D::operator-(const Vector2D & pOperando) const {
	Vector2D vector = *this;
	vector._x -= pOperando._x;
	vector._y -= pOperando._y;
	return vector;
}

double Vector2D::angulo() const {
	return atan2(_y, _x);
}